﻿using Furion.DatabaseAccessor;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using System;
using System.Linq.Expressions;

namespace Project1.EntityFramework.Core
{
    [AppDbContext("EQUConnectionString", DbProvider.Oracle)]
    public class EQUDbContext : AppDbContext<EQUDbContext>, IModelBuilderFilter
    {
        public EQUDbContext(DbContextOptions<EQUDbContext> options) : base(options)
        {
            // 启用实体数据更改监听
            EnabledEntityChangedListener = false;
            // 忽略空值更新
            //InsertOrUpdateIgnoreNullValues = true;
        }

        //实体构建之前
        public void OnCreating(ModelBuilder modelBuilder, EntityTypeBuilder entityBuilder, DbContext dbContext, Type dbContextLocator)
        {
            // 设置软删除表达式
            //var fakeDeleteQueryFilterExpression = FakeDeleteQueryFilterExpression(entityBuilder, dbContext);
            //if (fakeDeleteQueryFilterExpression == null) return;

            //entityBuilder.HasQueryFilter(fakeDeleteQueryFilterExpression);
        }

        /// <summary>
        /// 假删除过滤器
        /// </summary>
        /// <param name="entityBuilder"></param>
        /// <param name="dbContext"></param>
        /// <param name="filterValue"></param>
        /// <returns></returns>
        protected static LambdaExpression FakeDeleteQueryFilterExpression(EntityTypeBuilder entityBuilder, DbContext dbContext, object? filterValue = null)
        {
            IMutableEntityType metadata = entityBuilder.Metadata;
            Expression finialExpression = Expression.Constant(true);
            ParameterExpression parameterExpression = Expression.Parameter(metadata.ClrType, "u");

            // 假删除过滤器

            ConstantExpression constantExpression = Expression.Constant("is_delete");
            ConstantExpression right = Expression.Constant(filterValue ?? false);
            var fakeDeleteQueryExpression = Expression.Equal(Expression.Call(typeof(EF), "Property", new Type[1]
            {
                    typeof(bool)
            }, parameterExpression, constantExpression), right);
            finialExpression = Expression.AndAlso(finialExpression, fakeDeleteQueryExpression);

            return Expression.Lambda(finialExpression, parameterExpression);
        }

        //启用批量操作
        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {

            base.OnConfiguring(optionsBuilder);
        }

        /// <summary>
        /// 重写保存之前事件
        /// </summary>
        /// <param name="eventData"></param>
        /// <param name="result"></param>
        //protected override void SavingChangesEvent(DbContextEventData eventData, InterceptionResult<int> result)
        //{
        //    // 获取当前事件对应上下文
        //    DbContext dbContext = eventData.Context!;

        //    // 强制重新检查一边实体更改信息
        //    // dbContext.ChangeTracker.DetectChanges();

        //    // 获取所有更改，删除，新增的实体，但排除审计实体（避免死循环）
        //    var entities = dbContext.ChangeTracker.Entries()
        //       .Where(u => u.Entity.GetType() != typeof(SysLog) && (u.State == EntityState.Modified || u.State == EntityState.Deleted || u.State == EntityState.Added))
        //       .ToList();

        //    // 通过请求中获取当前操作人
        //    //var userId = App.GetService<IHttpContextAccessor>().HttpContext.Items["UserId"];

        //    // 获取所有已更改的实体
        //    foreach (var entity in entities)
        //    {
        //        // 获取实体类型
        //        var entityType = entity.Entity.GetType();

        //        // 获取所有实体有效属性，排除 [NotMapper] 属性
        //        var props = entity.OriginalValues.Properties;

        //        // 获取实体当前（现在）的值
        //        var currentValues = entity.CurrentValues;

        //        // 获取数据库中实体的值
        //        var databaseValues = entity.GetDatabaseValues();

        //        var dataList = new List<toTable>();
        //        string key = "";
        //        // 遍历所有属性
        //        foreach (var prop in props)
        //        {
        //            // 获取属性名
        //            var propName = prop.Name;

        //            if (currentValues[propName] != null)
        //            {
        //                // 获取现在的实体值
        //                string newValue = "";
        //                if (prop.IsPrimaryKey())
        //                {
        //                    key = currentValues[propName].ToString();
        //                }
        //                newValue = currentValues[propName].ToString();
        //                string oldValue = "";
        //                // 如果是新增数据，则 databaseValues 为空，所以需要判断一下
        //                if (databaseValues != null)
        //                {
        //                    if (databaseValues[propName] != null)
        //                        oldValue = databaseValues[propName].ToString();
        //                }
        //                if (newValue != oldValue)
        //                {
        //                    var baseData = new toTable(propName, newValue, oldValue);

        //                    dataList.Add(baseData);
        //                }
        //            }
        //        }
        //        var data = Clay.Object(dataList);
        //        _Log.InsertAsync(new SysLog
        //        {
        //            id = YitIdHelper.NextId(),
        //            table = entityType.Name,    // 表名
        //            key = key,
        //            create_time = DateTime.Now, // 操作时间
        //            json = data.ToString(),
        //            user_id = App.User.FindFirstValue("userID"),    // 操作人
        //            operate = entity.State.ToString()  // 操作方式：新增、更新、删除
        //        });
        //    }
        //}
    }
}